﻿using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using UnityEditor;
using UnityEditor.Callbacks;
using UnityEditor.iOS.Xcode;
using UnityEngine;
#if  UNITY_IOS&&!DEVELOP
using System.Runtime.InteropServices;
#endif


namespace QQSDK
{
    public class PostBuild : MonoBehaviour
    {
#if UNITY_EDITOR || DEVELOP
#elif UNITY_IOS && !DELSDK
        [DllImport("__Internal")]
        private static extern void showIDFAToast();
#elif UNITY_ANDROID
#elif UNITY_WEBGL

#else

#endif
        private static extern void init();
        public bool enable = true;
        private static SDKData data; //所有数据

        static void LoadConfig()
        {
            data = JsonMapper.ToObject<SDKData>(File.ReadAllText(Application.dataPath + "/QQSDK/Ads/Res/" + "sdkConfig.json"));
        }

        [PostProcessBuild]
        public static void OnPostprocessBuild(BuildTarget buildTarget, string path)
        {

            if (buildTarget == BuildTarget.iOS)
            {
                string xcodeProjectPath = "/Unity-iPhone.xcodeproj/project.pbxproj";
                string projPath = path + xcodeProjectPath;
                PBXProject proj = new PBXProject();
                proj.ReadFromString(File.ReadAllText(projPath));

#if UNITY_2020||UNITY_2019_3||UNITY_2019_4
                string target = proj.GetUnityFrameworkTargetGuid();
#else
                string target = proj.GetUnityFrameworkTargetGuid();
#endif
#if DEVELOP
                SDKFunc.Log("开发模式");
                RemoveMMFiles(path, proj, target);
#else
                SDKFunc.Log("正式模式");
                LoadConfig(); //加载配置文件信息
                AddFrameWork(path, proj, target);
                SetAdsInit(path);
                ChangeInfoPlistFile(path); //修改info plist文件
                EnablePushNotificationDef(path); //打开推送宏定义开关
                CreatePodFile(path); //创建podfile
#endif
                SavePBXProject(projPath, proj);
            }
        }
        static void RemoveMMFiles(string path, PBXProject proj, string target)
        {
            string folderPath = Path.Combine(path, "Libraries/Plugins/iOS");
            DirectoryInfo directory = new DirectoryInfo(folderPath);

            if (Directory.Exists(folderPath))
            {
                FileInfo[] fileInfos = directory.GetFiles();
                foreach (var item in fileInfos)
                {
                    proj.RemoveFile(proj.FindFileGuidByProjectPath(Path.Combine("Libraries/Plugins/iOS", item.Name)));
                }
            }
            else
            {
                SDKFunc.Log("文件夹不存在");
            }
        }
        private static void AddFrameWork(string path, PBXProject proj, string target)
        {

            CreateAdsConfigFile(path, proj, target); //创建AdsConfig文件
            //enable iap
            proj.AddCapability(target, PBXCapabilityType.InAppPurchase);
            proj.AddCapability(target, PBXCapabilityType.PushNotifications);
            proj.AddCapability(target, PBXCapabilityType.KeychainSharing);
            proj.AddCapability(target, PBXCapabilityType.BackgroundModes);

            proj.AddBuildProperty(target, "OTHER_LDFLAGS", "-ObjC");
            proj.SetBuildProperty(target, "ENABLE_BITCODE", "NO");

            proj.AddBuildProperty(target, "HEADER_SEARCH_PATHS", "$(SRCROOT)/Libraries/Plugins/iOS/ADController.h");

            proj.AddFrameworkToProject(target, "AVFoundation.framework", false);
            proj.AddFrameworkToProject(target, "CoreGraphics.framework", false);
            proj.AddFrameworkToProject(target, "CoreLocation.framework", false);
            proj.AddFrameworkToProject(target, "CoreMedia.framework", false);
            proj.AddFrameworkToProject(target, "CoreTelephony.framework", false);
            proj.AddFrameworkToProject(target, "Foundation.framework", false);
            proj.AddFrameworkToProject(target, "MediaPlayer.framework", false);
            proj.AddFrameworkToProject(target, "MessageUI.framework", false);
            proj.AddFrameworkToProject(target, "QuartzCore.framework", false);
            proj.AddFrameworkToProject(target, "SafariServices.framework", false);
            proj.AddFrameworkToProject(target, "StoreKit.framework", false);
            proj.AddFrameworkToProject(target, "SystemConfiguration.framework", false);
            proj.AddFrameworkToProject(target, "UIKit.framework", false);
            proj.AddFrameworkToProject(target, "WebKit.framework", false);
            //TT
            proj.AddFrameworkToProject(target, "CoreMotion.framework", false);
            proj.AddFrameworkToProject(target, "libc++.tbd", false);
            proj.AddFrameworkToProject(target, "libresolv.9.tbd", false);
            proj.AddFrameworkToProject(target, "AdSupport.framework", false);

            proj.AddFrameworkToProject(target, "Photos.framework", false);
            proj.AddFrameworkToProject(target, "AssetsLibrary.framework", false);
            proj.AddFrameworkToProject(target, "MobileCoreServices.framework", false);
            proj.AddFrameworkToProject(target, "StoreKit.framework", false);
            proj.AddFrameworkToProject(target, "AssetsLibrary.framework", false);
            proj.AddFrameworkToProject(target, "UserNotifications.framework", false);
            proj.AddFrameworkToProject(target, "libxml2.2.tbd", false);
        }
        static void SavePBXProject(string path, PBXProject proj)
        {
            File.WriteAllText(path, proj.WriteToString());
        }
        /// <summary>
        /// 更改info.plist文件
        /// </summary>
        /// <param name="path"></param>
        public static void ChangeInfoPlistFile(string path)
        {
            string infoPlistFileName = "/Info.plist";
            string plistPath = path + infoPlistFileName;
            PlistDocument plist = new PlistDocument();
            plist.ReadFromString(File.ReadAllText(plistPath));
            PlistElementDict rootDict = plist.root;
            PlistElementArray array = rootDict.CreateArray("LSApplicationQueriesSchemes");
            array.AddString("instagram");
            rootDict.SetString("NSPhotoLibraryUsageDescription", "The App needs your permission to access the album"); //App需要您的同意,才能访问相册
            rootDict.SetString("NSCameraUsageDescription", "The App needs your consent to use AR function"); //App需要您的同意,才能访问相机
            rootDict.SetString("NSUserTrackingUsageDescription", "he App needs your consent to Tracking AD"); //App需要您的同意,才能追踪广告
            rootDict.SetString("AppLovinSdkKey", "y0QuLBT7doLvislQLZlCHP4sqbZb-cbwc1pzCG4q3QimGSBb0xoHLt89ShlRJLMwM9uZQzNUN5EeXQETL1qgvz"); //设置applovin sdk key
            rootDict.SetString("GADApplicationIdentifier", data.appleStore.admobData.app_id); //设置admob app id

            PlistElementArray skuArray = rootDict.CreateArray("SKAdNetworkItems");
            File.WriteAllText(plistPath, plist.WriteToString());
        }

        static void CreatePodFile(string rootPath)
        {
            StringBuilder sb = new StringBuilder();
            string allText = File.ReadAllText(Application.dataPath + "/QQSDK/Ads/Res/Podfile");
#if UNITY_2020||UNITY_2019_3||UNITY_2019_4
            string podText = allText.Replace("Unity-iPhone", "UnityFramework");
#else
            string podText = allText;
#endif
            //sb.Append("pod 'KKAds','1.7.3.100'")
            //    .Append("\n")
            //    .Append("pod 'KKUtils','1.1.1'")
            //    .Append("\n")
            //    .Append("pod 'KKAnalytics','1.5.5'");

            string podfileString = podText.Replace("###$$###", sb.ToString());
            StreamWriter sw = File.CreateText(Path.Combine(rootPath, "Podfile"));
            sw.WriteAsync(podfileString);
            sw.Flush();
            sw.Close();
        }

        /// <summary>
        /// Imports the header file to unity app contrller file.在ios启动项目中添加导入头文件代码
        /// </summary>
        /// <param name="originCodeText">Origin code text.</param>
        /// <param name="importText">Import text.</param>
        static void ImportHeaderFileToUnityAppContrllerFile(List<string> originCodeText, params string[] importText)
        {
            for (int i = 0; i < importText.Length; i++)
            {
                originCodeText.Insert(i, importText[i]);
            }
        }
        /// <summary>
        /// Adds the code text to unity app controller file 在ios启动项中，指定字段后，添加代码
        /// </summary>
        /// <param name="originCodeText">Origin code text.</param>
        /// <param name="targetText">Target text.</param>
        /// <param name="addCodeText">Add code text.</param>
        static void ModifyCodeTextToUnityAppControllerFile(List<string> originCodeText, string targetText, params string[] addCodeText)
        {
            int targetRow = -1;
            for (int i = 0; i < originCodeText.Count; i++)
            {
                if (originCodeText[i].Contains(targetText))
                {
                    targetRow = i;
                }
            }
            if (targetRow == -1)
                return;
            for (int i = addCodeText.Length - 1; i >= 0; i--)
            {
                originCodeText.Insert(targetRow + 1, addCodeText[i]);
            }
        }
        static void AddMethodInUnityAppController(List<string> originCodeText, string addCodeText, string targetText)
        {
            int targetRow = -1;
            for (int i = 0; i < originCodeText.Count; i++)
            {
                if (originCodeText[i].Contains(targetText))
                {
                    targetRow = i;
                }
            }
            if (targetRow == -1)
                return;
            originCodeText.Insert(targetRow - 1, addCodeText);
        }

        static void EnablePushNotificationDef(string path)
        {
            string unityDefaultRemoteNotificationReplaceSymbolsString = "UNITY_USES_REMOTE_NOTIFICATIONS 0";
            string unityPreprocessorFilePath = "/Classes/Preprocessor.h";
            string unityDefaultRemoteNotificationString = "UNITY_USES_REMOTE_NOTIFICATIONS 1";
            string preprocessorPath = path + unityPreprocessorFilePath;
            string text = File.ReadAllText(preprocessorPath);
            text = text.Replace(unityDefaultRemoteNotificationReplaceSymbolsString, unityDefaultRemoteNotificationString);
            File.WriteAllText(preprocessorPath, text);
        }
        static void CreateAdsConfigFile(string rootPath, PBXProject pBXProject, string targetGUID)
        {
            string templateAdsConfig = File.ReadAllText(Application.dataPath + "/QQSDK/Ads/Res/" + "AdsConfig.plist");
            string appIDFormatString = "<key>om_app_key</key>\n<string>{0}</string>";
            string bannerIDFormatString = "<key>om_banner_id</key>\n<string>{0}</string>";
            string splash_id_formatStrig = "<key>om_splash_id</key>\n<string>{0}</string>";

            string splashShowFormatString = "<key>sp_im</key>\n<string>{0}</string>";
            string bannerShowFormatString = "<key>ba_im</key>\n<string>{0}</string>";
            string interstitialShowFormatString = "<key>in_im</key>\n<string>{0}</string>";
            string rewardVideoShowFormatString = "<key>re_im</key>\n<string>{0}</string>";

            StringBuilder sb = new StringBuilder();
            sb.Append(string.Format(appIDFormatString, data.appleStore.openMediationData.app_id)) //OM key
                .Append("\n")
                .Append(string.Format(bannerIDFormatString, data.appleStore.openMediationData.banner_id)) //OM Banner ID
                .Append("\n")
                .Append(string.Format(splash_id_formatStrig, data.appleStore.openMediationData.splash_id)) //OM Splash ID
                .Append("\n")
                .Append(string.Format(splashShowFormatString, data.appleStore.adjustData.splash_im_token))
                .Append("\n")
                .Append(string.Format(bannerShowFormatString, data.appleStore.adjustData.banner_im_token))
                .Append("\n")
                .Append(string.Format(interstitialShowFormatString, data.appleStore.adjustData.interstitial_im_token))
                .Append("\n")
                .Append(string.Format(rewardVideoShowFormatString, data.appleStore.adjustData.rewardvideo_im_token));
            string adsConfigText = templateAdsConfig.Replace("###$$###", sb.ToString());
            StreamWriter sw = File.CreateText(Path.Combine(rootPath, "AdsConfig.plist"));
            sw.WriteAsync(adsConfigText);
            sw.Flush();
            sw.Close();
            string guid = pBXProject.AddFile(Path.Combine(rootPath, "AdsConfig.plist"), "AdsConfig.plist", PBXSourceTree.Source);
        }
        static void SetAdsInit(string rootPath)
        {
            string kkAnalyticsHeaderString = "#import <QQSdkTool/QQSdkAnalyticsTool.h>";
            string kkInitManagerHeaderString = "#import <QQSdkTool/QQSDKInitManager.h>";
            string kkAdsHeaderString = "#import \"ADController.h\"";
            string idfaHeaderString = "#import <AppTrackingTransparency/AppTrackingTransparency.h>";
            string launchingReplaceSymbolsString = "::printf(\"-> applicationDidFinishLaunching()\\n\");";
            string launchingBecomeActiveString = "::printf(\"-> applicationDidBecomeActive()\\n\");";
            string firebaseInitString = "[[QQSdkAnalyticsTool shareManager]initFirebase];";
            string registerNotificationWhenAppLaunchString = "[[QQSdkAnalyticsTool shareManager]registerNotificationWhenAppLaunch:application];";
            //string reyundataFormat = "[[KKAnalytics shareManager]initTracking:@\"{0}\"];";
            string thinkingdataFormat = "[[QQSDKInitManager sharedInstance]initSDKWithConfig];";
            string attributiondataFormat = "[[QQSDKInitManager sharedInstance]initAttribution];";
            string attributionStratdataFormat = "[[QQSDKInitManager sharedInstance]startSdkAttribution];";
            string showIDFAToast = @"
       if (@available(iOS 14.5, *)){
        [ATTrackingManager requestTrackingAuthorizationWithCompletionHandler:^(ATTrackingManagerAuthorizationStatus status) {
          // 获取到权限后，依然使用老方法获取idfa
          if (status == ATTrackingManagerAuthorizationStatusAuthorized) {
            NSString *idfa = [[ASIdentifierManager sharedManager].advertisingIdentifier UUIDString];
            NSLog(@""%@"",idfa);
          } else {
            NSLog(@""请在设置-隐私-跟踪中允许App请求跟踪"");
          }
        }];
      }else{
        NSString *idfa = [[ASIdentifierManager sharedManager].advertisingIdentifier UUIDString];
        NSLog(@""%@"",idfa);
      };";
            //string adjustFormat = "[[KKAnalytics shareManager]initAdjust:@\"{0}\"];";
            //string adjustSecretIDFormat = "[[KKAnalytics shareManager]initAdjust:@\"{0}\"  secretID:{1} info1:{2} info2:{3} info3:{4} info4:{5}];";
            string adsInitString = "[ADController instance];";
            //string facebookFormat = "[[KKAnalytics shareManager]initFacebook:@\"{0}\"];";
            string didRegisterForRemoteNotificationsWithDeviceTokenReplaceSymbolString = "UnitySendDeviceToken(deviceToken);";
            string registerNotificationWithDiveceToken = "[[QQSdkAnalyticsTool shareManager]registerNotificationWithDiveceToken:deviceToken];";
            string didRegisterUserNotificationSettingsMethodString = "- (void)application:(UIApplication *)application didRegisterUserNotificationSettings:(UIUserNotificationSettings *)notificationSettings{  [[QQSdkAnalyticsTool shareManager]registerNotificationSetting:application];}";
            string applicationWillResignActiveMethodString = "- (void)applicationWillResignActive:(UIApplication*)application";
            string appDelegateClassName = "/Classes/UnityAppController.mm";
            string adjustText = string.Empty;
            //if (!data.appleStore.adjustData.enable_secrets)
            //{
            //    adjustText = string.Format(adjustFormat, data.appleStore.adjustData.app_token);
            //}
            //else
            //{
            //    adjustText = string.Format(adjustSecretIDFormat,
            //        data.appleStore.adjustData.app_token,
            //        data.appleStore.adjustData.secretID,
            //        data.appleStore.adjustData.info1,
            //        data.appleStore.adjustData.info2,
            //        data.appleStore.adjustData.info3,
            //        data.appleStore.adjustData.info4);
            //}
            //string reyunText = string.Format(reyundataFormat, data.appleStore.reyunData.app_id);
            string modifyClassPath = Path.GetFullPath(rootPath) + appDelegateClassName;
            string[] lines = File.ReadAllLines(modifyClassPath);
            List<string> info = lines.ToList();

            string firebaseString = string.Empty;

            if (data.googleStore.crashAnalyticsData.enable)
            {
                firebaseString = firebaseInitString;
            }
            if (data.appleStore.crashAnalyticsData.enable)
            {
                firebaseString = firebaseInitString;
            }
            string byteDanceString = string.Empty;

            ImportHeaderFileToUnityAppContrllerFile(info, new string[]
            {
                kkAdsHeaderString,
                kkAnalyticsHeaderString,
                kkInitManagerHeaderString,
                idfaHeaderString
            });
            ModifyCodeTextToUnityAppControllerFile(info, launchingReplaceSymbolsString, new string[]
            {
   
                //string.Format(thinkingdataFormat, data.appleStore.thinkingData.app_id),
               
                thinkingdataFormat,
                adsInitString,
                attributiondataFormat,
                firebaseString,
                registerNotificationWhenAppLaunchString,
                byteDanceString
            });
            ModifyCodeTextToUnityAppControllerFile(info, launchingBecomeActiveString, new string[]
            {
                attributionStratdataFormat,
                showIDFAToast,
                byteDanceString
            });
            //添加第三方sdk的启动项
            //获取deviceid
            ModifyCodeTextToUnityAppControllerFile(info, didRegisterForRemoteNotificationsWithDeviceTokenReplaceSymbolString, new string[] { registerNotificationWithDiveceToken });
            //获取deviceid
            AddMethodInUnityAppController(info,
                didRegisterUserNotificationSettingsMethodString,
                applicationWillResignActiveMethodString
            );
            File.WriteAllLines(modifyClassPath, info.ToList<string>());
        }

    }
}